<?php

/**
 * +--------------------------------------------------------------
 * | eLuoPHP
 * +--------------------------------------------------------------
 * | Copyright (c) 2016-2018 http://qxwoo.cn All rights reserved.
 * +--------------------------------------------------------------
 * | y139w [y139w@163.com]
 * +--------------------------------------------------------------
 * | 应用处理类文件
 * +--------------------------------------------------------------
 */

namespace luo;

use luo\exception\ClassNotFoundException;
use luo\exception\RouterException;
use luo\ioc\Ioc;
use ReflectionException;

class Application{

    /**
     * 运行应用
     * @param Response $response
     * @return object
     * @throws ReflectionException
     */
	public static function initialize(Response $response){

        // 获取控制器对象，与方法名
	    $application = Ioc::make(self::class, 'init');
	    // 执行方法，获取数据
	    $data = Ioc::make($application['object'], $application['action']);
	    if($data instanceof Response){
            $response = $data;
        }else{
            $response = $response->create($data);
        }
		return $response;
		
	}

    /**
     * 初始化配置
     * @return array|mixed|null
     */
	private static function initConfig(){

	    // 加载应用配置
        Config::load(CONF_PATH . 'config' . CONFIG_EXT);
        // 加载数据库配置
        Config::load(CONF_PATH . 'database' . CONFIG_EXT, 'database');
        return Config::get();

    }

    /**
     * @param Request $request
     * @param Router $router
     * @return array
     * @throws ClassNotFoundException
     * @throws ReflectionException
     * @throws RouterException
     */
	public static function init(Request $request, Router $router){
	    // 初始化配置
	    $config = self::initConfig();
        // 设置系统时区
        date_default_timezone_set($config['default_timezone']);
        // 注册命名空间
        Loader::instance()->addNamespaceArray(include CONF_PATH . 'namespace' . CONFIG_EXT);
        // 获取当前请求的PATH_INFO
        $pathinfo = trim($request->pathinfo(), '/');
        // 获取$_GET的所有参数
        $getArgs = $request->get();
        $getArgs = $getArgs ? $getArgs : [];
        // 路径拼接
        $path = trim(implode('?', [$pathinfo ? $pathinfo : $config['default_action'], http_build_query($getArgs)]), '?');
        //判断是否使用强制路由
        if($config['url_route_must']){
            $files = $config['route_config_file'];
            foreach($files as $file){
                $routes = include ROUTE_PATH . $file . CONFIG_EXT;
                if(is_array($routes)){
                    // 注册路由
                    $router->register($routes);
                }
            }
            // 验证路由
            $result = $router->check($path);
        }else{
            $result = $router->parseUrl($path);
        }
        if(!$result){
            throw new RouterException($request->pathinfo());
        }
        return self::local( $request, $result);
    }

    /**
     * @param Request $request
     * @param $result
     * @return array
     * @throws ClassNotFoundException
     * @throws ReflectionException
     */
    public static function local(Request $request,  $result){

        // 初始化配置
        $config = self::initConfig();
        // 模块
        $module = $result[0] ?? $config['default_module'];
        $request->module($module);
        $module = strtolower($module);

        // 控制器
        $controller = $result[1] ?? $config['default_controller'];
        $request->controller($controller);
        $controller = (strtolower($controller));

        // 方法
        $action = $result[2] ?? $config['default_action'];
        $request->action($action);
        $action = strtolower($action);

        // 命令行执行
        if(PHP_SAPI === 'cli'){
            // 获取参数
            $argv = ($request->server('argv'));
            if(isset($argv[1])){
                // 处理参数
                $rule = explode('/', $argv[1]);
                $request->module($module = ($rule[0] ? strtolower($rule[0]) : $config['default_module']));
                $request->controller($controller = ($rule[1] ? strtolower($rule[1]) : $config['default_controller']));
                $request->action($action = ($rule[2] ? strtolower($rule[2]) : $config['default_action']));
            }
        }
        // 要执行的类
        $class = '\\app\\' . $module . '\\controller\\' . ucwords($controller);
        // 执行控制器
        if (class_exists($class)) {
            $object = Ioc::instance($class);
            return ['object'=>$object, 'action'=>$action];
        }else{
            throw new ClassNotFoundException($class);
        }
    }
	
}